home *** CD-ROM | disk | FTP | other *** search
/ Magnum One / Magnum One (Mid-American Digital) (Disc Manufacturing).iso / d12 / asmbler.arc / DETAB.ASM < prev    next >
Assembly Source File  |  1988-11-19  |  5KB  |  133 lines

  1. COMMENT \
  2. Filter a file, expanding tabs to blanks up to the next column which is a
  3. multiple of 8.
  4.  
  5. Usage:  detab <inputfile >outputfile
  6.  
  7. {Adapted from a disassembly  of the IBM  utility MORE.COM and  commented
  8. with a view to being a model for further simple filters.}
  9. [20-Jan-84]
  10. \
  11.  
  12. assume  cs:detabc,ds:detabc,es:detabc,ss:detabc
  13. detabc  segment para public 'code'
  14.  
  15. include dos.inc
  16. include ascii.inc
  17.  
  18.         org     100h
  19. MAXBUFFER       equ     4096    ; Buffer size (freely variable)
  20.  
  21. detab:
  22.         mov     ah,$DOS_GETVERSION
  23.         int     $DOS
  24.         xchg    ah,al
  25.         cmp     ax,0200h        ; DOS 2.00 or later?
  26.         jnb     cont            ; jump if version >= 2.00
  27.         mov     dx,offset baddos
  28.         mov     ah,$DOS_STROUT  ; print string
  29.         int     $DOS
  30.         mov     ah,$DOS_EXIT
  31.         mov     al,1            ; return code
  32.         int     $DOS            ; terminate
  33.  
  34. cont:
  35.         mov     byte ptr numrows,25
  36.         mov     ah,0fh          ; request current video state
  37.         int     $VIDEO
  38.         mov     numcols,ah      ; save number of columns on display
  39.         mov     bx,$STDIN       ; standard input handle
  40.         mov     ah,$DOS_DUP     ; dup handle
  41.         int     $DOS
  42.         mov     bp,ax           ; save duplicate handle
  43.         mov     ah,$DOS_CLOSE2  ; close standard input
  44.         int     $DOS
  45.         mov     bx,$STDERR      ; standard error handle
  46.         mov     ah,$DOS_DUP     ; dup handle
  47.         int     $DOS
  48.  
  49. nextbf:
  50.         cld                     ; clear direction flag
  51.         mov     dx,offset buffer        ; buffer address
  52.         mov     cx,MAXBUFFER    ; count of bytes to read
  53.         mov     bx,bp           ; duplicate of standard input handle
  54.         mov     ah,$DOS_READ2   ; byte stream
  55.         int     $DOS            ; read a byte string
  56.         or      ax,ax           ; set condition flags based on byte count
  57.         jnz     gotch           ; jump if got some bytes
  58. exit:
  59.         mov     ah,$DOS_EXIT    ; all done, no more data
  60.         mov     al,0            ; return code
  61.         int     $DOS            ; terminate
  62.  
  63. gotch:
  64.         mov     cx,ax           ; byte count
  65.         mov     si,dx           ; buffer address ???
  66. nextch:
  67.         lodsb                   ; load byte at 0(si), then increment si
  68.         cmp     al,.CR          ; Hit CR yet?
  69.         jne     nocr            ; Jump if not CR
  70.         mov     byte ptr colnum,1       ; Was CR, set column_number = 1
  71.         jmp     short printch   ; go print the character
  72. nocr:
  73.         cmp     al,.LF          ; Hit end-of-line yet?
  74.         jne     nolf            ; Jump if not LF
  75.         inc     rownum          ; Hit LF, increment row number
  76.         jmp     short printch   ; go print the character
  77. nolf:
  78.         cmp     al,.BS          ; Hit backspace?
  79.         jne     nobs            ; Jump if not BS
  80.         cmp     byte ptr colnum,1       ; At beginning of line?
  81.         jz      printch         ; Yes, just print character
  82.         dec     colnum          ; No, decrement column number because of BS
  83.         jmp     short printch   ; Go print the character
  84. nobs:
  85.         cmp     al,.HT          ; Hit tab?
  86.         jne     notab           ; Jump if not tab.
  87.         mov     ah,colnum       ; Was tab, get column number
  88.         add     ah,7            ; column number + 7
  89.         and     ah,not 7        ; clear right 3 bits, effectively advancing
  90.         inc     ah              ; to multiple of 8, then add 1 more
  91.         mov     colnum,ah       ; and update column number
  92.         jmp     short printch   ; Go print the character
  93. notab:
  94.         cmp     al,.BEL         ; Hit a bell?
  95.         je      printch         ; Yes, just print it
  96.         inc     colnum          ; Not special character, so just increment
  97.         mov     ah,colnum       ; column number and remember it
  98.         cmp     ah,numcols      ; At end of screen line yet?
  99.         jbe     printch         ; jump if not
  100.         inc     rownum          ; At end of screen line, so start a new row
  101.         mov     byte ptr colnum,1       ; and reset to column 1
  102. printch:
  103.         mov     dl,al           ; the character to output
  104.         mov     ah,$DOS_CONOUT  ; print char
  105.         int     $DOS
  106.         mov     ah,rownum
  107.         cmp     ah,numrows      ; At end of screen yet?
  108.         jb      loopch          ; Jump if not
  109.         mov     byte ptr colnum,1       ; Reset row/column to home
  110.         mov     byte ptr rownum,1       ; position
  111.         dec     si              ; Backup in buffer
  112.         inc     cx              ; and increase byte count (why ??)
  113. loopch:
  114.         dec     cx              ; Reduce byte count since we just output one
  115.         jbe     longbf          ; Exit loop if count <= 0
  116.         jmp     nextch          ; Otherwise loop for next character
  117. longbf:
  118.         jmp     nextbf          ; Loop for next buffer
  119.  
  120. numrows db      24              ; Default screen rows
  121. numcols db      80              ; Default screen columns
  122. rownum  db      01              ; Starting screen row
  123. colnum  db      01              ; Starting screen column
  124.         db      00h,00h,00h,00h,00h
  125. baddos  db      "DETAB: Incorrect DOS version"
  126.         db      " -- must run under DOS 2.0 or later"
  127. crlf    db      .CR,.LF,"$"
  128.  
  129. buffer  db      MAXBUFFER dup (0)       ; Input buffer
  130.  
  131. detabc  ends
  132.         end     detab
  133.